
//
// Source code recreated from a .class file by IntelliJ IDEA
// (powered by Fernflower decompiler)
//

package com.wsd.smartcarwasher.service;

import com.wsd.smartcarwasher.configuration.mqtt.MqttGateway;
import com.wsd.smartcarwasher.constans.MachineEvent;
import com.wsd.smartcarwasher.domain.Machine;
import com.wsd.smartcarwasher.domain.MessageRecord;
import com.wsd.smartcarwasher.domain.OrderInfo;
import com.wsd.smartcarwasher.domain.Partner;
import com.wsd.smartcarwasher.util.DateUtil;
import com.wsd.smartcarwasher.util.HttpUtil;
import com.wsd.smartcarwasher.util.StringUtil;
import org.json.JSONObject;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Lazy;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import javax.smartcardio.CardNotPresentException;
import java.io.File;
import java.math.BigDecimal;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;

@Service
public class MqttService {
    private static final Logger logger = LoggerFactory.getLogger(MqttService.class);
    @Resource
    private MqttGateway mqttGateway;
    @Resource
    @Lazy
    private OrderService orderService;
    @Autowired(required = false)
    private MachineService machineService;
    @Resource
    private RecordService recordService;
    @Resource
    private PartnerService partnerService;
    @Resource
    private RedisService redisService;
    @Resource
    private UserInfoService userInfoService;

    //判断车辆位置
    public static Map<String,String> carIsStop = new HashMap<>();
    @Resource
    @Lazy
    private LappService lappService;

    public MqttService() {
    }

    boolean sendMsg(String topic, String msg) {
        try {
            this.mqttGateway.sendToMqtt(topic, 2, msg);
            logger.info(String.format("send message: topic[ %s ], message[ %s ]", topic, msg));
            return true;
        } catch (Exception var4) {
            logger.error("sendMessage fail: " + var4.getMessage());
            return false;
        }
    }

    private void replyMessage(String machineId, JSONObject message) {
        message.put("ack", true);
        this.sendMsg(machineId, message.toString());
    }
    public void receiveMessage(JSONObject jsonObject) {
        if (!jsonObject.has("ack")) {
            String machineId = null;
            if (jsonObject.has("machineId")) {
                machineId = jsonObject.getString("machineId");
                this.replyMessage(machineId, jsonObject);
            } else {
                logger.info("no parameter named machineId from mqtt message");
            }
            String orderSn = null;
            if (jsonObject.has("orderSn")) {
                orderSn = jsonObject.getString("orderSn");
            } else {
                logger.info("no parameter named orderSn from mqtt message");
            }
            if (jsonObject.has("message")) {
                JSONObject message = jsonObject.getJSONObject("message");
                String eventCode=message.getString("messageCode");
                MachineEvent machineEvent = MachineEvent.matchEvent(eventCode);
                if (machineEvent == null) {
                    logger.info("find no matched event by eventCode:" + eventCode);
                } else {
                    try {
                        if ("A".equalsIgnoreCase(machineEvent.getLevel())) {
                            this.recordService.addRecord(new MessageRecord(machineId, orderSn, machineEvent, jsonObject.toString()));
                            this.levelAEvent(machineId, orderSn, machineEvent);
                        } else if ("B".equalsIgnoreCase(machineEvent.getLevel())) {
                            this.recordService.addRecord(new MessageRecord(machineId, orderSn, machineEvent, jsonObject.toString()));
                        } else if ("C".equalsIgnoreCase(machineEvent.getLevel())) {
                            this.levelCEvent(machineId, orderSn, machineEvent);
                        } else if ("D".equalsIgnoreCase(machineEvent.getLevel())) {
                            this.levelDEvent(machineId, machineEvent, message);
                        }else if("F".equalsIgnoreCase(machineEvent.getLevel())){
                            this.recordService.addRecord(new MessageRecord(machineId, orderSn, machineEvent, jsonObject.toString()));
                            this.levelFEvent(machineId, orderSn, machineEvent);
                        }
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                    WebSocketServer.sendInfo(machineEvent.toJsonString(), machineId);
                }
            } else {
                logger.info("no parameter named message from mqtt message");
            }
            //保存洗车前后图片
            try {
                saveImg(jsonObject);
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }


    private void levelAEvent(String machineId, String orderSn, MachineEvent machineEvent) {
        logger.info(String.format("level A event handle, machineId [ %s ], orderSn [%s ], eventCode [ %s ]", machineId, orderSn, machineEvent.getEventCode()));
        if (MachineEvent.A_01.equals(machineEvent)) {
            Machine machine = new Machine();
            machine.setId(Integer.parseInt(machineId));
            machine.setStatus(2);
            if (this.machineService.updateMachine(machine) == 0) {
                logger.info(String.format("fail to change machine with id %s to Closed", machineId));
            }
            OrderInfo orderInfo = new OrderInfo();
            orderInfo.setOrderSn(orderSn);
            orderInfo.setEndTime(new Date());
            orderInfo.setConsumed(2);
            if (this.orderService.updateOrder(orderInfo) == 0) {
                logger.info("fail to change order to consumed, orderSn:" + orderSn);
            }
            //紧急停止后结账
            orderInfo = this.orderService.queryOrderInfoByOrderSn(orderSn);
            machine = this.machineService.queryMachineById(Integer.parseInt(machineId));
            if (machine != null && machine.getPartnerId() != null) {
                Partner partner = this.partnerService.getPartnerById(machine.getPartnerId());
                if (partner != null) {
                    BigDecimal accountBefore = partner.getAccount();
                    BigDecimal account = orderInfo.getPayPrice().multiply(machine.getProfitRatio()).add(accountBefore);
                    partner.setAccount(account);
                    if (this.partnerService.updatePartner(partner) == 0) {
                        logger.info(String.format("fail to add profit to partner, partnerId [ %s ], account before [ %s ], account after [ %s ], profitRate [ %s ]", partner.getId(), accountBefore, account, machine.getProfitRatio()));
                    }
                }
            }
        }
    }
    public void levelCEvent(String machineId, String orderSn, MachineEvent machineEvent) {
        logger.info(String.format("level C event handle, machineId [ %s ], orderSn [%s ], eventCode [ %s ]", machineId, orderSn, machineEvent.getEventCode()));
        OrderInfo order;
        if (MachineEvent.C_16.equals(machineEvent)) {
            BigDecimal orderPrice = new BigDecimal(0);
            order = this.orderService.queryOrderInfoByOrderSn(orderSn);
            if (order != null) {
                orderPrice = order.getPayPrice();
                order = new OrderInfo();
                order.setOrderSn(orderSn);
                order.setConsumed(1);
                order.setEndTime(new Date());
                order.setServiceStatus(1);
                if (this.orderService.updateOrder(order) == 0) {
                    logger.info(String.format("fail to change order to consumed, orderSn [ %s ]  time [ %s ]", orderSn, order.getEndTime()));
                }
                //订单消费成功,在t_order表中插入最后一次支付的时间节点
//                logger.info("订单消费成功,在t_order表中插入最后一次支付的时间节点"+orderSn);
                String beforePayTime=this.orderService.queryByLatelyUserId(orderSn);

                if(beforePayTime!=null)
                {
                    Date beforeTime= DateUtil.convertStringToDate(beforePayTime);
                    int days = (int) ((System.currentTimeMillis() - beforeTime.getTime()) / (1000*3600*24));
                    this.orderService.updatePayNode(order.getOrderSn(),days);
                }
            }
            if (machineId != null) {
                if (this.machineService.changeMachineWorkStateUnOccupied(Integer.parseInt(machineId)) == 0) {
                    logger.info(String.format("fail to change machine to unOccupied, machineId [ %s ]", machineId));
                }
                Machine machine = this.machineService.queryMachineById(Integer.parseInt(machineId));
                if(!StringUtil.isNullOrEmpty(machine))
                {
                    //开始机器，保存洗车图片
                    try{
                        this.lappService.saveOrderCarWashImage(this.orderService.queryOrderInfoByOrderSn(orderSn),machine);
                    }catch (Exception e)
                    {
                        logger.info("保存洗车图片失败");
                        e.printStackTrace();
                    }
                }
                if (machine != null && machine.getPartnerId() != null) {
                    Partner partner = this.partnerService.getPartnerById(machine.getPartnerId());
                    if (partner != null) {
                        BigDecimal accountBefore = partner.getAccount();
                        BigDecimal account = orderPrice.multiply(machine.getProfitRatio()).add(accountBefore);
                        partner.setAccount(account);
                        if (this.partnerService.updatePartner(partner) == 0) {
                            logger.info(String.format("fail to add profit to partner, partnerId [ %s ], account before [ %s ], account after [ %s ], profitRate [ %s ]", partner.getId(), accountBefore, account, machine.getProfitRatio()));
                        }
                    }
                }
            }
        }
        else if (MachineEvent.C_01.equals(machineEvent)) {
            int machineChangeRows = this.machineService.changeMachineWorkStateOccupied(Integer.parseInt(machineId));
            if (machineChangeRows == 0) {
                logger.info("fail to change machine to unOccupied, machineId:" + machineId);
            }
            order = new OrderInfo();
            order.setOrderSn(orderSn);
            order.setConsumed(1);
            order.setStartTime(new Date());
            order.setServiceStatus(0);
            this.orderService.updateOrder(order);
        }
    }


//    public static void main(String[] args) {
//        String date1="2020-07-15 19:11:16.0";
////        String date2="2020-05-14 04:24:29";
//        Date date= DateUtil.convertStringToDate(date1);
////        Date date11= DateUtil.convertStringToDate(date2);
////        int days = (int) ((date.getTime() - date11.getTime()) / (1000*3600*24));
//        System.out.println(date);
//    }

    private void levelDEvent(String machineId, MachineEvent machineEvent, JSONObject message) {
        int online;
        if (MachineEvent.D_01.equals(machineEvent)) {
            online = message.getInt("status");
            if (online != 1 && online != 0) {
                logger.info(String.format("illegal status status, params is %s", message));
                return;
            }
            Machine machine = new Machine();
            machine.setId(Integer.parseInt(machineId));
            machine.setStatus(1);
            machine.setOnline(1);
            machine.setWorkState(102);
            this.machineService.updateMachine(machine);
            //this.machineService.changeMachineOnlineState(machineId, online);
        } else if (MachineEvent.D_02.equals(machineEvent)) {
            online = message.getInt("status");
            if (online != 1 && online != 0) {
                logger.info(String.format("illegal online status, params is %s", message));
                return;
            }

            this.machineService.changeMachineOnlineState(machineId, online);
        }else if(MachineEvent.D_03.equals(machineEvent))
        {
            online = message.getInt("status");
            //新加的机器状态
            if(online==1)
            {
                Machine machine = new Machine();
                machine.setId(Integer.parseInt(machineId));
                machine.setStatus(1);
                machine.setWorkState(102);
                this.machineService.updateMachine(machine);
            }else if(online==3)
            {
                Machine machine = new Machine();
                machine.setId(Integer.parseInt(machineId));
                machine.setStatus(2);
                machine.setOnline(0);
                machine.setWorkState(102);
                this.machineService.updateMachine(machine);
            }
        }
        //设备复位成功后 修改 设备在线状态  和 工作状态
        else if (MachineEvent.D_100.equals(machineEvent)) {
            Machine machine = new Machine();
            machine.setId(Integer.parseInt(machineId));
            machine.setStatus(1);
            machine.setWorkState(102);
            this.machineService.updateMachine(machine);
        }

    }


    private void levelFEvent(String machineId, String orderSn, MachineEvent machineEvent) {
        logger.info(String.format("level F event handle, machineId [ %s ], orderSn [%s ], eventCode [ %s ]", machineId, orderSn, machineEvent.getEventCode()));
        OrderInfo orderInfo = new OrderInfo();
        orderInfo.setOrderSn(orderSn);
        orderInfo.setConsumed(3);
        orderInfo.setEndTime(new Date());
        if (this.orderService.updateOrder(orderInfo) == 0) {
            logger.info("fail to change order to consumed, orderSn:" + orderSn);
        }

    }



    public void saveImg(JSONObject jsonObject){
        String machineId = null;
        if (jsonObject.has("machineId")) {
            machineId = jsonObject.getString("machineId");
        } else {
            logger.info("no parameter named machineId from mqtt message");
        }
        String orderSn = null;
        if (jsonObject.has("orderSn")) {
            orderSn = jsonObject.getString("orderSn");
        } else {
            logger.info("no parameter named orderSn from mqtt message");
        }
        if (jsonObject.has("message")) {
            JSONObject message = jsonObject.getJSONObject("message");
            String eventCode = message.getString("messageCode");
            MachineEvent machineEvent = MachineEvent.matchEvent(eventCode);
            if (machineEvent == null) {
                logger.info("find no matched event by eventCode:" + eventCode);
            } else {
                String img= jsonObject.has("getimage")?jsonObject.getString("getimage") : "";
                if ("D".equalsIgnoreCase(machineEvent.getLevel())) {
                    if(MachineEvent.D_03.equals(machineEvent) ||
                            MachineEvent.D_04.equals(machineEvent) ||
                                MachineEvent.D_05.equals(machineEvent)){
                            logger.info("判断车辆是否停到位置了 :"+jsonObject.toString());
                            carIsStop.put("carStopIsOk_"+machineId,jsonObject.toString());
                            //redisService.put("carStopIsOk_"+machineId,jsonObject.toString(),10);
                    }
                }else if ("E".equalsIgnoreCase(machineEvent.getLevel())) {
                    if(MachineEvent.E_01.equals(machineEvent) && !img.equals("")){
                        redisService.put("queue_up_img"+machineId,img,120);
                    }
                    if(MachineEvent.E_02.equals(machineEvent) && !img.equals("")){
                        try{
                            HttpUtil.saveImg(img,System.getProperty("user.dir")+ File.separator+"smartwashImages"+File.separator+orderSn+"start"+".jpg");
                        }catch (Exception e){
                            logger.error("保存洗车前图片失败["+machineId+"]");
                        }
                    }
                } else if ("C".equalsIgnoreCase(machineEvent.getLevel())) {
                    //this.levelCEvent(machineId, orderSn, machineEvent);
                    if(MachineEvent.C_16.equals(machineEvent) && !img.equals("")){
                        try{
                            HttpUtil.saveImg(img,System.getProperty("user.dir")+ File.separator+"smartwashImages"+File.separator+orderSn+"end"+".jpg");
                        }catch (Exception e){
                            logger.error("保存洗车前后图片失败["+machineId+"]");
                        }
                    }
                }
            }
        } else {
            logger.info("no parameter named message from mqtt message");
        }
    }
}
/*
package com.wsd.smartcarwasher.service;

import com.wsd.smartcarwasher.configuration.mqtt.MqttGateway;
import com.wsd.smartcarwasher.constans.Global;
import com.wsd.smartcarwasher.constans.MachineEvent;
import com.wsd.smartcarwasher.domain.MessageRecord;
import com.wsd.smartcarwasher.domain.OrderInfo;
import org.json.JSONObject;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.Date;

@Service
public class MqttService {
    private static final Logger logger = LoggerFactory.getLogger(MqttService.class);

    @Resource
    private MqttGateway mqttGateway;

    @Resource
    private OrderService orderService;

    @Resource
    private MachineService machineService;

    @Resource
    private RecordService recordService;

    boolean sendMsg(String topic, String msg) {
        try {
            mqttGateway.sendToMqtt(topic, 2, msg);
        }catch (Exception e) {
            logger.error("sendMessage fail: " + e.getMessage());
            return false;
        }
        return true;
    }

    public void receiveMessage(JSONObject jsonObject) {
        MessageRecord messageRecord = new MessageRecord();
        String machineId = null;
        if (jsonObject.has("machineId")) {
            machineId = jsonObject.getString("machineId");
            messageRecord.setMachineId(machineId);
        } else {
            logger.info("no parameter named machineId from mqtt message");
        }
        String orderSn = null;
        if (jsonObject.has("orderSn")) {
            orderSn = jsonObject.getString("orderSn");
            messageRecord.setOrderSn(orderSn);
        } else {
            logger.info("no parameter named orderSn from mqtt message");
        }
        if (jsonObject.has("message")){
            String eventCode = jsonObject.getJSONObject("message").getString("messageCode");
            MachineEvent machineEvent = MachineEvent.matchEvent(eventCode);
            if (machineEvent == null) {
                logger.info("find no matched event by eventCode:" + eventCode);
            } else {
                if (Global.MACHINE_EVENT_LEVEL_C.equalsIgnoreCase(machineEvent.getLevel())) {
                    levelCEvent(machineId, orderSn, machineEvent);
                }
                WebSocketServer.sendInfo(machineEvent.toJsonString(), machineId);

                messageRecord.setLevel(machineEvent.getLevel());
                messageRecord.setEventCode(machineEvent.getEventCode());
                messageRecord.setEventMessage(machineEvent.getEventMessage());
            }
        } else {
            logger.info("no parameter named message from mqtt message");
        }
        messageRecord.setMessage(jsonObject.toString());
        messageRecord.setRecordTime(new Date());
        recordService.addRecord(messageRecord);
    }

    private void levelCEvent(String machineId, String orderSn, MachineEvent machineEvent) {
        if (MachineEvent.C_16.equals(machineEvent)) {
            OrderInfo orderInfo = new OrderInfo();
            orderInfo.setOrderSn(orderSn);
            orderInfo.setConsumed(Global.ORDER_IS_CONSUMED);
            orderInfo.setEndTime(new Date());
//            int changeRows = orderService.updateOrder(orderInfo);
//            if (changeRows == 0) {
//                logger.info("fail to change order to consumed, orderSn:" + orderSn);
//            }
            int machineChangeRows = machineService.changeMachineWorkStateUnOccupied(Integer.parseInt(machineId));
            if (machineChangeRows == 0) {
                logger.info("fail to change machine to unOccupied, machineId:" + machineId);
            }
        } else if (MachineEvent.C_01.equals(machineEvent)) {
            int machineChangeRows = machineService.changeMachineWorkStateOccupied(Integer.parseInt(machineId));
            if (machineChangeRows == 0) {
                logger.info("fail to change machine to unOccupied, machineId:" + machineId);
            }
            OrderInfo orderInfo = new OrderInfo();
            orderInfo.setOrderSn(orderSn);
            orderInfo.setStartTime(new Date());
            orderService.updateOrder(orderInfo);
        }
    }
}
*/
